/**
 * 
 */
package zzzhc.image.recognize;

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import javax.imageio.ImageIO;

import zzzhc.image.recognize.filter.BinaryFilter;
import zzzhc.image.recognize.filter.BorderFilter;
import zzzhc.image.recognize.filter.ContinueSplitFilter;
import zzzhc.image.recognize.filter.NormalizeFilter;

/**
 * @author <a href="mailto:zzzhc.starfire@gmail.com">zzzhc</a>
 */
public class TemplateCreator {

	private String imageSourceDir;

	private String templateSavePath;

	public TemplateCreator(String imageSourceDir, String templateSavePath) {
		this.imageSourceDir = imageSourceDir;
		this.templateSavePath = templateSavePath;
	}

	public void generate(Filter filter) throws IOException {
		File dir = new File(imageSourceDir);
		File[] fs = dir.listFiles();
		Set<ImageToken> set = new HashSet<ImageToken>();
		for (int i = 0; i < fs.length; i++) {
			String name = fs[i].getName();
			int index = name.indexOf(".");
			String code = name.substring(0, index);
			BufferedImage bi = ImageIO.read(fs[i]);
			if (bi == null) {
				System.out.println("path:" + fs[i]);
				continue;
			}
			RecognizeContext ia2 = new RecognizeContext(bi);

			filter.doFilter(ia2);
			ImageToken[] tokens = ia2.getTokens().toArray(new ImageToken[0]);
			ia2.show();
			for (int x = 0; x < tokens.length; x++) {
				ImageToken token = tokens[x];
				if (x < code.length()) {
					token.code = code.charAt(x);
					set.add(token);
					token.show();
				} else {
					System.err.println("code length mismatch:" + name);
				}
			}
		}

		System.out.println("token size=" + set.size());

		PrintWriter pw = new PrintWriter(new FileOutputStream(templateSavePath));
		for (Iterator<ImageToken> iter = set.iterator(); iter.hasNext();) {
			ImageToken ele = iter.next();
			pw.println(ele.encode());
		}
		pw.flush();
		pw.close();

		List<ImageToken> tokenList = new ArrayList<ImageToken>();
		tokenList.addAll(set);
		Collections.sort(tokenList, new Comparator<ImageToken>() {

			public int compare(ImageToken o1, ImageToken o2) {
				return o1.code - o2.code;
			}

		});
		for (int i = 0; i < 10; i++) {
			save(tokenList, i);
		}
	}

	private void save(List<ImageToken> tokenList, int n) throws IOException {
		PrintWriter pw = new PrintWriter(
				new FileOutputStream("nn" + n + ".txt"));
		char current = (char) -1;
		int index = 0;
		int count = 0;
		Set<Character> codes = new HashSet<Character>();
		for (ImageToken token : tokenList) {
			codes.add(token.code);
		}

		for (ImageToken token : tokenList) {
			if (current != token.code) {
				current = token.code;
				index++;
				if (index > n + 1) {
					break;
				}
				count = 0;
			}
			if (count >= 4) {
				continue;
			}
			for (int y = 0; y < token.h; y++) {
				for (int x = 0; x < token.w; x++) {
					pw.append(String.valueOf(token.data[y][x])).append(".0;");
				}
			}
			for (int i = 0; i < 10; i++) {
				if ((char) ('0' + i) == token.code) {
					pw.append("1.0;");
				} else {
					pw.append("0.0;");
				}
			}
			pw.append(token.code);
			pw.append("\n");
			count++;
		}
		pw.flush();
		pw.close();
	}

	/**
	 * @param args
	 * @throws IOException
	 */
	public static void main(String[] args) throws IOException {
		createKingsoftTemplate();
	}

	public static void createKingsoftTemplate() throws IOException {
		Filter filter = new BinaryFilter();
		FilterManager manager = new FilterManager();
		manager.addFilter(filter);
		manager.addFilter(new BorderFilter());
		manager.addFilter(new ContinueSplitFilter());
		manager.addFilter(new NormalizeFilter());

		TemplateCreator creator = new TemplateCreator("kingsoft2",
				"template.kingsoft.data");
		creator.generate(manager);
	}

}
